﻿using CPPEI.Coolzon.Metadata;
using CPPEI.Coolzon.UI;
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Forms;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using System.Windows.Threading;
using System.Windows.Forms.Integration;
using System.IO;
using System.Resources;
using System.Reflection;
using CPPEI.Coolzon.UI.Views;
using CPPEI.Coolzon.Event.NCL;
using CPPEI.Coolzon.UI.Data;
using CPPEI.Coolzon.Event.Core;

namespace CPPEI.Coolzon.Theme.Default
{
    /// <summary>
    /// MainView.xaml 的交互逻辑
    /// </summary>
    public partial class MainView : CPPEI.Coolzon.UI.View, IMainView
    {
        private static bool isFirstReConnectWiew;
        private string CurrentSceneName;
        private DispatcherTimer dispatcherTime;
        private CPPEI.Coolzon.UI.Views.Windows.OverviewWindow overview;
        private Point OldPoint;
        private Hook hook;
        private System.Windows.Forms.Button btnView;
        private bool IsPressBtnView;
        private double sceneViewHeight = 0.0;

        WindowsFormsHost wfhTop;
        WindowsFormsHost wfhBottom;
        WindowsFormsHost wfhExpand;
        PictureBox topImg;
        PictureBox bottomImg;
        PictureBox expandImg;

        public MainView()
        {
            InitializeComponent();

            //this.MouseUp += MainView_MouseUp;
            //this.MouseMove+=MainView_MouseMove;
            isFirstReConnectWiew = true;
            hook = new Hook();
            hook.MouseLeftButtonUp += hook_MouseLeftButtonUp;
            hook.MouseLeftButtonMove += hook_MouseLeftButtonMove;

            this.Close += MainView_Close;
        }
        void hook_MouseLeftButtonMove(double x, double y)
        {
            Move(x, y);
        }

        void hook_MouseLeftButtonUp(double x, double y)
        {
            CloseOverview();
        }
        private void CloseOverview()
        {
            if (overview != null)
            {
                hook.UnLoadHook();

                UI.Part part = overview.Tag as UI.Part;
                part.Unfreeze();

                overview.Close();
                overview = null;
            }
        }
        void MainView_Close(UI.View view, bool isCancel)
        {
            CloseOverview();
        }
        private void Move(double x, double y)
        {
            if (overview == null || overview.GetViewRegion() == null) return;
            Point mousePoint = new Point(x, y);
            if (OldPoint.X < mousePoint.X)
            {
                //右
                overview.SetBorderPosionX(1, mousePoint.X - OldPoint.X);
            }
            else
            {
                //左
                overview.SetBorderPosionX(-1, OldPoint.X - mousePoint.X);
            }

            if (OldPoint.Y < mousePoint.Y)
            {
                //上
                overview.SetBorderPosionY(1, mousePoint.Y - OldPoint.Y);
            }
            else
            {
                //下
                overview.SetBorderPosionY(-1, OldPoint.Y - mousePoint.Y);
            }

            OldPoint = mousePoint;

            overview.OnViewRegionMoving();
        }

        protected override void OnActive()
        {
            base.OnActive();

            CPPEI.Coolzon.UI.Views.RenderView renderView = (CPPEI.Coolzon.UI.Views.RenderView)UI.UIContext.Current.RenderView;
            _ctlRenderViewBorder.Child = renderView;
            // 将事件远程处理模式的代理实例注册到事件总线上
            RemoteEventProxy.Instance.SetRenderView(renderView);

            Common.EventBus.Instance.Register(renderView);
            Common.EventBus.Instance.Register(sceneView);
            Common.EventBus.Instance.Register(controlPanel);
            Common.EventBus.Instance.Register(sceneNavigation);
            Common.EventBus.Instance.Register(header);
            Common.EventBus.Instance.Register(this);
            Common.EventBus.Instance.Register(jsControl);

            NCLEventBus.Register(renderView);
            NCLEventBus.Register(sceneView);
            NCLEventBus.Register(controlPanel);
            NCLEventBus.Register(sceneNavigation);
            NCLEventBus.Register(header);
            NCLEventBus.Register(this);
            NCLEventBus.Register(jsControl);

            CoreEventBus.Register(renderView);
            CoreEventBus.Register(sceneView);
            CoreEventBus.Register(controlPanel);
            CoreEventBus.Register(sceneNavigation);
            CoreEventBus.Register(header);
            CoreEventBus.Register(this);
            CoreEventBus.Register(jsControl);

            Common.EventBus.Create(ServiceProxy.ClientProxyManager.EVENTBUS_FLAGNAME).Register(renderView);

            // 显示第一个场景
            Metadata.Scene firstScene = UIContext.Current.Solution.Scenes.First();

            NCLEventBus.PublishAsync(new NCLOpenSceneEvent(SwitchMode.Replace,"",firstScene.Name,null));
        }

        protected override void OnDeactive()
        {
            CPPEI.Coolzon.UI.Views.RenderView renderView = (CPPEI.Coolzon.UI.Views.RenderView)UI.UIContext.Current.RenderView;
            _ctlRenderViewBorder.Child = null;
            // 从事件总线撤销注册
            Common.EventBus.Instance.Unregister(renderView);
            Common.EventBus.Instance.Unregister(sceneView);
            Common.EventBus.Instance.Unregister(controlPanel);
            Common.EventBus.Instance.Unregister(sceneNavigation);
            Common.EventBus.Instance.Unregister(header);
            Common.EventBus.Instance.Unregister(this);
            Common.EventBus.Instance.Unregister(jsControl);

            NCLEventBus.Unregister(renderView);
            NCLEventBus.Unregister(sceneView);
            NCLEventBus.Unregister(controlPanel);
            NCLEventBus.Unregister(sceneNavigation);
            NCLEventBus.Unregister(header);
            NCLEventBus.Unregister(this);
            NCLEventBus.Unregister(jsControl);

            CoreEventBus.Unregister(renderView);
            CoreEventBus.Unregister(sceneView);
            CoreEventBus.Unregister(controlPanel);
            CoreEventBus.Unregister(sceneNavigation);
            CoreEventBus.Unregister(header);
            CoreEventBus.Unregister(this);
            CoreEventBus.Unregister(jsControl);

            Common.EventBus.Create(ServiceProxy.ClientProxyManager.EVENTBUS_FLAGNAME).Unregister(renderView);

            // 使用了winForm控件，需要手动释放
            if (wfhTop != null)
            {
                topImg.Dispose();
                topImg = null;
                wfhTop.Child = null;
                wfhTop.Dispose();
                wfhTop = null;
            }
            if (wfhBottom != null)
            {
                bottomImg.Dispose();
                bottomImg = null;
                wfhBottom.Child = null;
                wfhBottom.Dispose();
                wfhBottom = null;
            }
            if (wfhExpand != null)
            {
                expandImg.Dispose();
                expandImg = null;
                wfhExpand.Child = null;
                wfhExpand.Dispose();
                wfhExpand = null;
            }

            base.OnDeactive();
        }


        private void expandImg_MouseDown(object sender, System.Windows.Forms.MouseEventArgs e)
        {
            //动画开始
            Common.EventBus.Instance.Publish(new AnimationBeginEvent("expand"));
            wfhExpand.Visibility = System.Windows.Visibility.Collapsed;

            //右侧展开
            if (_ctlGridCenter.ColumnDefinitions[1].Width == new GridLength(0))
            {
                GridLengthAnimation rightVisibleAnimation = new GridLengthAnimation();
                rightVisibleAnimation.From = new GridLength(0);
                rightVisibleAnimation.To = new GridLength(200);
                rightVisibleAnimation.Duration = new TimeSpan(0, 0, 0, 0, 500);
                rightVisibleAnimation.Completed += (senderAnimation, eAnimation) =>
                {
                    _ctlGridCenter.ColumnDefinitions[1].BeginAnimation(RowDefinition.HeightProperty, null);
                    _ctlGridCenter.ColumnDefinitions[1].Width = new GridLength(200);
                    //动画结束
                    Common.EventBus.Instance.Publish(new AnimationEndEvent("expand"));
                    wfhExpand.Visibility = System.Windows.Visibility.Visible;
                };
                _ctlGridCenter.ColumnDefinitions[1].BeginAnimation(ColumnDefinition.WidthProperty, rightVisibleAnimation);
            }
            //右侧收回
            else
            {
                GridLengthAnimation rightVisibleAnimation = new GridLengthAnimation();
                rightVisibleAnimation.From = new GridLength(200);
                rightVisibleAnimation.To = new GridLength(0);
                rightVisibleAnimation.Duration = new TimeSpan(0, 0, 0, 0, 500);
                rightVisibleAnimation.Completed += (senderAnimation, eAnimation) =>
                {
                    _ctlGridCenter.ColumnDefinitions[1].BeginAnimation(RowDefinition.HeightProperty, null);
                    _ctlGridCenter.ColumnDefinitions[1].Width = new GridLength(0);

                    //动画结束
                    Common.EventBus.Instance.Publish(new AnimationEndEvent());
                    wfhExpand.Visibility = System.Windows.Visibility.Visible;
                };
                _ctlGridCenter.ColumnDefinitions[1].BeginAnimation(ColumnDefinition.WidthProperty, rightVisibleAnimation);
            }
        }
        private void topImg_MouseDown(object sender, System.Windows.Forms.MouseEventArgs e)
        {
            //动画开始
            Common.EventBus.Instance.Publish(new AnimationBeginEvent());
            wfhTop.Visibility = System.Windows.Visibility.Collapsed;
            //头部展开
            if (gridLayout.RowDefinitions[0].Height == new GridLength(0))
            {
                GridLengthAnimation topVisibleAnimation = new GridLengthAnimation();
                topVisibleAnimation.From = new GridLength(0);
                topVisibleAnimation.To = new GridLength(66);
                topVisibleAnimation.Duration = new TimeSpan(0, 0, 0, 0, 500);
                topVisibleAnimation.Completed += (senderAnimation, eAnimation) =>
                {
                    gridLayout.RowDefinitions[0].BeginAnimation(RowDefinition.HeightProperty, null);
                    gridLayout.RowDefinitions[0].Height = new GridLength(66);
                    //动画结束
                    Common.EventBus.Instance.Publish(new AnimationEndEvent());
                    wfhTop.Visibility = System.Windows.Visibility.Visible;
                };
                gridLayout.RowDefinitions[0].BeginAnimation(RowDefinition.HeightProperty, topVisibleAnimation);
            }
            //头部收回
            else
            {
                GridLengthAnimation topVisibleAnimation = new GridLengthAnimation();
                topVisibleAnimation.From = new GridLength(66);
                topVisibleAnimation.To = new GridLength(0);
                topVisibleAnimation.Duration = new TimeSpan(0, 0, 0, 0, 500);
                topVisibleAnimation.Completed += (senderAnimation, eAnimation) =>
                {
                    gridLayout.RowDefinitions[0].BeginAnimation(RowDefinition.HeightProperty, null);
                    gridLayout.RowDefinitions[0].Height = new GridLength(0);
                    //动画结束
                    Common.EventBus.Instance.Publish(new AnimationEndEvent());
                    wfhTop.Visibility = System.Windows.Visibility.Visible;
                };
                gridLayout.RowDefinitions[0].BeginAnimation(RowDefinition.HeightProperty, topVisibleAnimation);
            }
        }
        private void bottomImg_MouseDown(object sender, System.Windows.Forms.MouseEventArgs e)
        {
            //动画开始
            Common.EventBus.Instance.Publish(new AnimationBeginEvent());
            wfhBottom.Visibility = System.Windows.Visibility.Collapsed;

            //底部展开
            if (_ctlGridCenter.RowDefinitions[1].Height == new GridLength(0))
            {
                GridLengthAnimation bottomVisibleAnimation = new GridLengthAnimation();
                bottomVisibleAnimation.From = new GridLength(0);
                bottomVisibleAnimation.To = new GridLength(sceneViewHeight);
                bottomVisibleAnimation.Duration = new TimeSpan(0, 0, 0, 0, 500);
                bottomVisibleAnimation.Completed += (senderAnimation, eAnimation) =>
                {
                    _ctlGridCenter.RowDefinitions[1].BeginAnimation(RowDefinition.HeightProperty, null);
                    _ctlGridCenter.RowDefinitions[1].Height = new GridLength(sceneViewHeight);
                    //动画结束
                    Common.EventBus.Instance.Publish(new AnimationEndEvent());
                    wfhBottom.Visibility = System.Windows.Visibility.Visible;
                };
                _ctlGridCenter.RowDefinitions[1].BeginAnimation(RowDefinition.HeightProperty, bottomVisibleAnimation);
            }
            //底部收回
            else
            {
                GridLengthAnimation bottomVisibleAnimation = new GridLengthAnimation();
                bottomVisibleAnimation.From = new GridLength(_ctlGridCenter.RowDefinitions[1].ActualHeight);
                bottomVisibleAnimation.To = new GridLength(0);
                bottomVisibleAnimation.Duration = new TimeSpan(0, 0, 0, 0, 500);
                bottomVisibleAnimation.Completed += (senderAnimation, eAnimation) =>
                {
                    _ctlGridCenter.RowDefinitions[1].BeginAnimation(RowDefinition.HeightProperty, null);
                    _ctlGridCenter.RowDefinitions[1].Height = new GridLength(0);
                    //动画结束
                    Common.EventBus.Instance.Publish(new AnimationEndEvent());
                    wfhBottom.Visibility = System.Windows.Visibility.Visible;
                };
                _ctlGridCenter.RowDefinitions[1].BeginAnimation(RowDefinition.HeightProperty, bottomVisibleAnimation);
            }
        }

        [Common.Subscribe]
        public void OnOpen(NCLOpenSceneEvent @event)
        {
            if (@event.State == NCLEventState.Finished)
            {
                this.Dispatcher.Invoke(() =>
                {
                    OnOpened(@event);
                });
            }
        }
        public void OnOpened(NCLOpenSceneEvent @event)
        {
            CreateImg();
        }
        [Common.Subscribe]
        public void SceneUpdate(SceneUpdateEvent @event)
        {
            if (sceneViewHeight == 0.0)
            {
                sceneViewHeight = _ctlGridCenter.ActualHeight * 0.3;
                _ctlGridCenter.RowDefinitions[1].Height = new GridLength(sceneViewHeight);
            }
        }

        private void InitDispatcherTime()
        {
            if (dispatcherTime == null)
            {
                dispatcherTime = new DispatcherTimer();
                dispatcherTime.Tick += dispatcherTime_Tick;
                dispatcherTime.IsEnabled = false;
                dispatcherTime.Interval = TimeSpan.FromMilliseconds(100);
            }
        }

        void dispatcherTime_Tick(object sender, EventArgs e)
        {
            if (System.Windows.Input.Mouse.LeftButton == MouseButtonState.Pressed)
            {
                Common.EventBus.Instance.Publish(new UI.Event.LoopSceneEvent(Convert.ToInt32(dispatcherTime.Tag), CurrentSceneName, 10));
            }
        }
        private void StopDispatcherTime()
        {
            if (dispatcherTime != null && dispatcherTime.IsEnabled)
            {
                dispatcherTime.Stop();
                dispatcherTime.IsEnabled = false;
            }
        }

        private void StartDispatcherTime(int direction)
        {
            dispatcherTime.Tag = direction;
            dispatcherTime.IsEnabled = true;
            dispatcherTime.Start();
        }

        private void CreateImg()
        {
            //创建Top按钮
            if (wfhTop == null)
            {
                wfhTop = new WindowsFormsHost();
                Grid.SetColumn(wfhTop, 0);
                Grid.SetRow(wfhTop, 0);
                wfhTop.Width = 146;
                wfhTop.Height = 46;
                wfhTop.VerticalAlignment = VerticalAlignment.Top;
                wfhTop.HorizontalAlignment = System.Windows.HorizontalAlignment.Center;

                topImg = new PictureBox();
                topImg.Image = GetImage("top.png");
                topImg.MouseDown += topImg_MouseDown;
                topImg.Cursor = System.Windows.Forms.Cursors.Hand;
                topImg.SizeMode = PictureBoxSizeMode.StretchImage;

                System.Windows.Controls.Panel.SetZIndex(wfhTop, 1);

                wfhTop.Child = topImg;
                _ctlGridCenter.Children.Add(wfhTop);
            }
            else
            {
                _ctlGridCenter.Children.Remove(wfhTop);
                _ctlGridCenter.Children.Add(wfhTop);
            }

            //创建Bottom按钮
            if (wfhBottom == null)
            {
                wfhBottom = new WindowsFormsHost();
                Grid.SetColumn(wfhBottom, 0);
                Grid.SetRow(wfhBottom, 0);
                wfhBottom.Width = 146;
                wfhBottom.Height = 46;
                wfhBottom.VerticalAlignment = VerticalAlignment.Bottom;

                bottomImg = new PictureBox();
                bottomImg.Image = GetImage("bottom.png");
                bottomImg.MouseDown += bottomImg_MouseDown;
                bottomImg.Cursor = System.Windows.Forms.Cursors.Hand;
                bottomImg.SizeMode = PictureBoxSizeMode.StretchImage;

                System.Windows.Controls.Panel.SetZIndex(wfhBottom, 1);

                wfhBottom.Child = bottomImg;

                _ctlGridCenter.Children.Add(wfhBottom);
            }
            else
            {
                _ctlGridCenter.Children.Remove(wfhBottom);
                _ctlGridCenter.Children.Add(wfhBottom);
            }

            //创建右边按钮
            if (wfhExpand == null)
            {
                wfhExpand = new WindowsFormsHost();
                Grid.SetColumn(wfhExpand, 0);
                Grid.SetRowSpan(wfhExpand, 2);
                wfhExpand.Width = 46;
                wfhExpand.Height = 146;
                wfhExpand.HorizontalAlignment = System.Windows.HorizontalAlignment.Right;
                wfhExpand.VerticalAlignment = VerticalAlignment.Center;

                expandImg = new PictureBox();
                expandImg.Image = GetImage("left.png");
                expandImg.MouseDown += expandImg_MouseDown;
                expandImg.Cursor = System.Windows.Forms.Cursors.Hand;
                expandImg.SizeMode = PictureBoxSizeMode.StretchImage;

                System.Windows.Controls.Panel.SetZIndex(wfhExpand, 1);

                wfhExpand.Child = expandImg;
                _ctlGridCenter.Children.Add(wfhExpand);
            }
            else
            {
                _ctlGridCenter.Children.Remove(wfhExpand);
                _ctlGridCenter.Children.Add(wfhExpand);
            }
        }

        void wfhView_PreviewTouchUp(object sender, TouchEventArgs e)
        {
            if (IsPressBtnView)
            {
                CloseOverview();
            }
        }

        void wfhView_PreviewTouchDown(object sender, TouchEventArgs e)
        {
            System.Drawing.Point startPoint = btnView.PointToScreen(new System.Drawing.Point(0, 0));
            System.Drawing.Point endPoint = btnView.PointToScreen(new System.Drawing.Point(btnView.Width, btnView.Height));

            Point touchPoint = PointToScreen(Mouse.GetPosition(this));
            if (touchPoint.X > startPoint.X && touchPoint.X < endPoint.X
                && touchPoint.Y > startPoint.Y && touchPoint.Y < endPoint.Y)
                Action(touchPoint);
        }
        void btnView_MouseDown(object sender, System.Windows.Forms.MouseEventArgs e)
        {
            Action(new Point(e.X, e.Y));
        }
        private void Action(Point point)
        {
            CPPEI.Coolzon.UI.Views.RenderView renderView = (CPPEI.Coolzon.UI.Views.RenderView)UI.UIContext.Current.RenderView;
            CPPEI.Coolzon.UI.Part screenPart = renderView.GetCurrentPart();
            //ImageSource imageSource = screenPart.ProjectionToImage();
            screenPart.Frozen();
            double scale = 0.1f;

            Rect viewRegion = new Rect();
            viewRegion.Width = renderView.ActualWidth;
            viewRegion.Height = renderView.ActualHeight;
            Point origionPoint = renderView.TranslatePoint(new Point(0, 0), screenPart);
            viewRegion.X = origionPoint.X;
            viewRegion.Y = origionPoint.Y;

            Point mousePtInScreen = point;

            //overview = new UI.Views.Windows.OverviewWindow(imageSource, scale,
            //    viewRegion, mousePtInScreen);
            overview = new UI.Views.Windows.OverviewWindow(screenPart, screenPart.XWidth, screenPart.XHeight,
                 scale,
                 viewRegion, mousePtInScreen);

            overview.Tag = screenPart;
            overview.ViewRegionMoved += overview_ViewRegionMoved;
            overview.ViewRegionMoving += overview_ViewRegionMoving;
            overview.Show();
            //IsPressBtnView = true;
            hook.SetMouseHook();
        }

        void overview_ViewRegionMoving(Size originalSize, Size fullSize, Rect viewRegion)
        {
            double scale = originalSize.Width / fullSize.Width;

            double offsetX = viewRegion.Left * scale;
            double offsetY = viewRegion.Top * scale;

            CPPEI.Coolzon.UI.Views.RenderView renderView = (CPPEI.Coolzon.UI.Views.RenderView)UI.UIContext.Current.RenderView;
            renderView.ScrollToPos(offsetX, offsetY);
        }

        void overview_ViewRegionMoved(Size originalSize, Size fullSize, Rect viewRegion)
        {
            if (overview != null)
            {
                overview.Close();
                overview = null;
            }
        }
        private System.Drawing.Image GetImage(string name)
        {
            string resourceName = this.GetType().Assembly.GetName().Name + ".g";
            ResourceManager rm = new ResourceManager(resourceName, this.GetType().Assembly);
            string fileName = "images/" + name;
            UnmanagedMemoryStream ums = rm.GetStream(fileName);

            return System.Drawing.Image.FromStream(ums);
        }

        //[Common.Subscribe]
        //public void OnReceiveNetStateFeedbackEvent(UI.Views.ClientProxyStateFeedbackEvent @event)
        //{
        //    this.Dispatcher.Invoke(() =>
        //    {
        //        if (!@event.IsConnected())
        //        {
        //            if (isFirstReConnectWiew)
        //            {
        //                CPPEI.Coolzon.UI.Views.ReConnectView reConnectView = new UI.Views.ReConnectView();
        //                UIContext.Current.RootViewContainer.PopView("消息", reConnectView);
        //                reConnectView.Close += reConnectView_Close;
        //                isFirstReConnectWiew = false;
        //            }
        //        }
        //    });
        //}

        [Common.Subscribe]
        public void SceneUpdated(SceneUpdateEvent @event)
        {
            if (IsFirstActive)
            {

            }
        }
        void reConnectView_Close(UI.View view, bool isCancel)
        {
            isFirstReConnectWiew = true;
        }
    }
}
